home *** CD-ROM | disk | FTP | other *** search
- # Source Generated with Decompyle++
- # File: in.pyo (Python 2.5)
-
- from __future__ import with_statement
- from gui.skin.skinobjects import SkinColor
- import wx
- from wx import RectPS, Rect, ITEM_NORMAL, ITEM_SEPARATOR, ITEM_CHECK, ITEM_RADIO, Point, ALIGN_CENTER_VERTICAL, FindWindowAtPoint, MenuItem, CallLater, FindWindowAtPointer, GetMousePosition, wxEVT_MOTION, StockCursor, CURSOR_DEFAULT, GetMouseState, Window
- from wx import PyCommandEvent, wxEVT_MENU_OPEN
- from gui import skin
- from traceback import print_exc
- from gui.textutil import default_font
- from gui.windowfx import fadein
- from gui.vlist.skinvlist import SkinVListBox
- from gui.uberwidgets.UberButton import UberButton
- from gui.skin.skinobjects import Margins
- from gui.uberwidgets.skinnedpanel import SkinnedPanel
- from gui.uberwidgets.keycatcher import KeyCatcher
- from cgui import SplitImage4
- from gui.toolbox import Monitor
- from util import traceguard, memoize, Delegate, Storage as S, InstanceTracker
- from common import prefprop
- from weakref import ref
- from logging import getLogger
- log = getLogger('umenu')
- wxMSW = 'wxMSW' in wx.PlatformInfo
- WM_INITMENUPOPUP = 279
-
- def MenuItem_repr(item):
- text = None if item.IsSeparator() else item.Label
- return '<%s %s>' % (item.__class__.__name__, text)
-
- MenuItem.__repr__ = MenuItem_repr
- del MenuItem_repr
-
- MenuItem.SetCallback = lambda item, callback: item.Menu.SetCallback(item.Id, callback)
-
- class UMenuTrayTimer(wx.Timer):
-
- def __init__(self, umenu):
- wx.Timer.__init__(self)
- self.umenu = umenu
-
-
- def Notify(self):
-
- try:
- mp = GetMousePosition()
- ms = GetMouseState()
- except Exception:
- return None
-
- if not ms.LeftDown() and ms.RightDown() or ms.MiddleDown():
- return None
-
- menu = self.umenu
- while menu != None:
- if menu.ScreenRect.Contains(mp):
- return None
- continue
- submenu = menu.menu._childmenu
- menu = None if submenu is not None else None
- self.Stop()
- self.umenu.Dismiss()
-
-
-
- class UMenu(wx.Menu, InstanceTracker):
- last_menu = None
-
- def __init__(self, parent, label = '', id = None, onshow = None, windowless = None):
- if not isinstance(parent, wx.WindowClass):
- raise TypeError('UMenu parent must be a wx.Window')
-
- wx.Menu.__init__(self, label)
- InstanceTracker.track(self)
- if not isinstance(id, (int, type(None))):
- raise TypeError
-
- self._parentmenu = None
- self._childmenu = None
- self.Id = None if id is None else id
- self.Window = parent
- self.OnDismiss = Delegate()
- self.cbs = { }
- if onshow is not None:
- self.Handler.AddShowCallback(self.Id, (lambda menu = (ref(self),): onshow(menu())))
-
- if wxMSW:
- self.Handler.hwndMap[self.HMenu] = self
-
- self._windowless = windowless
- self.UpdateSkin()
-
-
- def SetWindowless(self, val):
- self._windowless = val
-
- Windowless = property((lambda self: self._windowless), SetWindowless)
-
- def IsShown(self):
- if not self.popup:
- return False
-
-
- try:
- return self.popup.IsShown()
- except AttributeError:
- return False
-
-
-
- def UpdateSkin(self):
- mbskin = skin.get('MenuBar', None)
- if 'wxMac' in wx.PlatformInfo and not mbskin and mbskin.get('menuskin', None) is None or mbskin.get('mode', 'skin').lower() == 'native':
- self.skin = S(native = True)
- native = True
- else:
- self.skin = skin.get(mbskin.menuskin)
- native = False
- self.skin.native = False
- if not native and not hasattr(self, 'popup'):
- self.popup = MenuPopupWindow(self.Window, self)
- elif not native:
- self.popup.UpdateSkin()
- self.popup.vlist.UpdateSkin()
- elif native:
- if hasattr(self, 'popup'):
- self.popup.Destroy()
- del self.popup
-
-
-
-
- def Display(self, caller = None):
- self.PopupMenu(caller.ScreenRect)
-
-
- def dismiss_old(self):
- menuref = UMenu.last_menu
- if menuref is None:
- return None
-
- menu = menuref()
- if menu is not None and not wx.IsDestroyed(menu):
- menu.Dismiss()
-
- UMenu.last_menu = None
-
-
- def PopupMenu(self, pos = None, submenu = False, event = None):
- if not submenu:
- self.dismiss_old()
-
- if event is not None:
- event.Skip(False)
-
- if 'wxMSW' in wx.PlatformInfo and self._windowless:
- _smokeFrame = _smokeFrame
- import gui.native.win.wineffects
- if _smokeFrame:
- _smokeFrame.SetFocus()
-
-
-
- try:
- onshow = self._onshow
- except AttributeError:
- pass
-
- onshow(self)
- traceguard.__enter__()
-
- try:
- return popup(pos)
- finally:
- pass
-
-
-
- def Dismiss(self):
- if not self.skin.get('native', False) and not wx.IsDestroyed(self.popup):
- return self.popup.vlist.Dismiss()
-
-
- if wxMSW:
- if hasattr(wx.Menu, 'GetHMenu'):
- GetHMenu = wx.Menu.GetHMenu
- else:
-
- def GetHMenu(self):
- cast = cast
- POINTER = POINTER
- c_long = c_long
- import ctypes
- p = cast(int(self.this), POINTER(c_long))
- return p[25]
-
- HMenu = property(GetHMenu)
-
-
- def AddItem(self, text = '', bitmap = None, callback = None, id = -1):
- return self._additem(text, bitmap, callback, id = id)
-
-
- def AddItemAt(self, position, text = '', bitmap = None, callback = None, id = -1):
- return self._additem(text, bitmap, callback, id = id, position = position)
-
-
- def Append(self, id, text, bitmap = None, callback = None):
- return self._additem(text, bitmap, callback, id = id)
-
-
- def AddCheckItem(self, text, callback = None):
- return self._additem(text, callback = callback, kind = ITEM_CHECK)
-
-
- def AddRadioItem(self, text, callback = None):
- return self._additem(text, callback = callback, kind = ITEM_RADIO)
-
-
- def AddPrefCheck(self, pref, text, help = '', updatenow = True):
- profile = profile
- import common
- prefs = profile.prefs
-
- def callback():
- prefs[pref] = not prefs[pref]
-
- item = self._additem(text, callback = callback, kind = ITEM_CHECK)
- prefs.link((pref,), (lambda val: item.Check(val)), obj = self)
- return item
-
-
- def AppendLazyMenu(self, name, callback, bitmap = None):
- if not callable(callback):
- raise TypeError, repr(callback)
-
- menu = UMenu(self.Window)
- return self.AddSubMenu(menu, name, bitmap = bitmap, onshow = (lambda menu = (menu,): callback(menu)))
-
-
- def _additem(self, text, bitmap = None, callback = None, kind = ITEM_NORMAL, id = -1, position = None):
- item = MenuItem(self, id, text, kind = kind)
- id = item.Id
- if bitmap is not None:
- self.SetItemBitmap(item, bitmap)
-
- if callback is not None:
- self.SetCallback(id, callback)
-
- if position is None:
- self.AppendItem(item)
- else:
- self.InsertItem(position, item)
- return item
-
-
- def SetCallback(self, id, callback):
-
- callback = lambda cb = (callback,): self._refresh_callback(cb)
- self.cbs[id] = callback
- self.Handler.AddCallback(id, callback)
-
-
- def _refresh_callback(self, cb):
- m = self._parentmenu
- if m is None:
- m = self
- else:
- while m._parentmenu:
- m = m._parentmenu
- if hasattr(m, '_button'):
- if wx.IsDestroyed(m._button):
- del m._button
- else:
- m._button.Refresh()
- m._button.Update()
-
- self.Window.Refresh()
- self.Window.Update()
- return cb()
-
-
- def AddSubMenu(self, submenu, label, bitmap = None, onshow = None):
- submenu._parentmenu = self
- if onshow is not None:
- self.Handler.AddShowCallback(submenu.Id, onshow)
-
- item = self.AppendSubMenu(submenu, label)
- if bitmap is not None:
- self.SetItemBitmap(item, bitmap)
-
- return item
-
-
- def SetItemBitmap(self, item, bitmap):
- if self.skin.native and bitmap.Ok():
- bitmap = bitmap.ResizedSmaller(16)
-
- item.SetBitmap(bitmap)
-
-
- def AddSep(self):
- return self.AppendItem(MenuItem(self))
-
-
- def AddSepAt(self, i):
- return self.InsertItem(i, MenuItem(self))
-
-
- def RemoveItems(self, items):
- return [ self.RemoveItem(item) for item in items ]
-
-
- def RemoveAll(self):
- return self.RemoveItems(list(self))
-
-
- def DestroyAll(self):
- for item in self.RemoveAll():
- item.Destroy()
-
-
-
- def GetItemById(self, id):
- for i, myitem in enumerate(self):
- if myitem.Id == id:
- return myitem
- continue
-
-
-
- def IndexOf(self, item):
- id = item.Id
- for i, myitem in enumerate(self):
- if myitem.Id == id:
- return i
- continue
-
- return -1
-
-
- def Break(self):
- raise NotImplementedError('skinned menus cannot break')
-
-
- def Top(self):
- w = self.Window
- while not isinstance(w, wx.TopLevelWindow):
-
- try:
- w = getattr(w, 'Window', getattr(w, 'ParentWindow', w.Parent))
- continue
- except AttributeError:
- print '***', w, '***'
- raise
- continue
-
-
- None<EXCEPTION MATCH>AttributeError
- return w
-
- Top = property(Top)
-
- def Handler(self):
- return menuEventHandler(self.Top)
-
- Handler = property(Handler)
-
- def _activate_item(self, item):
- return self.popup.vlist._activate_item(item)
-
-
- def __iter__(self):
- return iter(self.GetMenuItems())
-
-
- def __getitem__(self, n):
- return self.GetMenuItems()[n % len(self)]
-
-
- def __len__(self):
- return len(self.GetMenuItems())
-
-
- def __contains__(self, item):
- for i in self:
- if i.Id == item.Id:
- return True
- continue
-
- return False
-
-
- def __repr__(self):
- return '<%s %r>' % (self.__class__.__name__, self.Title)
-
-
-
- class UMenuBar(wx.MenuBar):
-
- def __init__(self, parent, skinkey = 'MenuBar'):
- wx.MenuBar.__init__(self)
- self.toptitles = { }
- self.skinkey = skinkey
- self.accelremoves = Delegate()
- self.panel = SkinnedPanel(parent, 'MenuBar')
- self.panel.UpdateSkin = self.UpdateSkin
- self.panel.Hide()
- self.UpdateSkin()
-
-
- def UpdateSkin(self):
- s = self.skin = skin.get(self.skinkey)
- if not s.get('mode', 'skin').lower() == 'native':
- pass
- self.native = 'wxMac' in wx.PlatformInfo
- if not hasattr(self, 'panel'):
- return None
-
- if self.native:
- for child in self.panel.Children:
- traceguard.__enter__()
-
- try:
- child.Destroy()
- finally:
- pass
-
-
- self.panel.Hide()
- self.ParentWindow.Top.SetMenuBar(self)
- else:
- self._constructSkinElements()
- win = self.ParentWindow.Top
- if win.MenuBar is self:
- win.SetMenuBar(None)
-
- self.panel.Sizer.Layout()
- self.panel.Show(self.IsShown())
-
-
- def Append(self, menu, title, onshow = None):
- self.toptitles[menu] = title
- i = wx.MenuBar.Append(self, menu, title)
- if not self.native:
- self._constructSkinElements()
-
- if onshow is not None:
- self.Handler.AddShowCallback(menu.Id, (lambda menu = (menu,): onshow(menu)))
-
- return i
-
-
- def _constructSkinElements(self):
- s = self.skin
- p = self.panel
- p.bg = s.get('background', SkinColor(wx.WHITE))
- pad = p.padding = s.get('padding', wx.Point(0, 0))
- for child in list(p.Children):
- child.Hide()
- child.Destroy()
-
- v = wx.BoxSizer(wx.VERTICAL)
- h = wx.BoxSizer(wx.HORIZONTAL)
- v.Add(h, 1, wx.EXPAND | wx.TOP | wx.BOTTOM, pad.y)
- p.Sizer = s.get('margins', Margins()).Sizer(v)
- self.buttons = []
- addb = self.buttons.append
- menus = self.Menus
- nummenus = len(self.Menus)
- for menu, label in enumerate(menus):
- del menu.OnDismiss[:]
- label = self.toptitles.get(menu, label)
- button = UberButton(p, -1, skin = s.itemskin, label = label, type = 'menu', menu = menu, menubarmode = True)
- addb(button)
- menu._next = menus[(i + 1) % nummenus][0]
- menu._prev = menus[i - 1][0]
- menu._button = button
-
- (h.AddMany,)((lambda .0: for b in .0:
- (b, 0, wx.EXPAND | wx.LEFT, pad.x))(self.buttons))
- self._bindAccelerators()
-
-
- def Show(self, val):
- native = self.native
- if native:
- win = self.ParentWindow.Top
- self.panel.Hide()
- if val and win.MenuBar is not self:
- win.MenuBar = self
- elif not val and win.MenuBar is self:
- win.MenuBar = None
-
- else:
- self.panel.Show(val)
-
-
- def _bindAccelerators(self):
- accelrems = self.accelremoves
- parentproc = self.ParentWindow.ProcessEvent
- keybind = self.KeyCatcher.OnDown
- accelrems()
- del accelrems[:]
- for menu in self:
- for item in menu:
- accel = GetAccelText(item)
- if accel:
-
- cb = lambda e, item = item, menu = (menu,): parentproc(menuevt(item))
- accelrems.append(keybind(accel, cb))
- continue
-
-
-
-
- def KeyCatcher(self):
-
- try:
- return self.ParentWindow._keycatcher
- except AttributeError:
- k = self.ParentWindow._keycatcher = KeyCatcher(self.ParentWindow)
- return k
-
-
- KeyCatcher = property(KeyCatcher)
-
- def __len__(self):
- return self.GetMenuCount()
-
-
- def __iter__(self):
- return []([ self.GetMenu(i) for i in xrange(self.GetMenuCount()) ])
-
-
- def SizableWindow(self):
- return self.panel
-
- SizableWindow = property(SizableWindow)
-
- def ParentWindow(self):
- return self.panel.Parent
-
- ParentWindow = property(ParentWindow)
-
- def Handler(self):
- return menuEventHandler(self.panel.Top)
-
- Handler = property(Handler)
-
- registered_activate_app = False
-
- def _activateapp(e):
- vlist = MenuListBox._lastvlist()
- if vlist is not None and not wx.IsDestroyed(vlist) and not wx.IsDestroyed(vlist.menu):
- if vlist.menu and vlist.menu._windowless and not e.GetActive():
- vlist.DismissRoot()
-
-
-
-
- class MenuListBox(SkinVListBox):
-
- def __init__(self, parent, menu):
- global registered_activate_app
- SkinVListBox.__init__(self, parent, style = wx.NO_BORDER | wx.FULL_REPAINT_ON_RESIZE | wx.WANTS_CHARS)
- self.menu = menu
- self.UpdateSkin()
- self.timer = wx.PyTimer(self._on_submenu_timer)
- Bind = self.Bind
- Bind(wx.EVT_MOUSE_EVENTS, self._mouseevents)
- Bind(wx.EVT_MOUSE_CAPTURE_CHANGED, self._capturechanged)
- Bind(wx.EVT_LISTBOX, self._listbox)
- Bind(wx.EVT_KEY_DOWN, self._keydown)
- self.mouseCallbacks = {
- wx.wxEVT_MOTION: self._motion,
- wx.wxEVT_RIGHT_DOWN: self._rdown,
- wx.wxEVT_LEFT_DOWN: self._ldown,
- wx.wxEVT_LEFT_UP: self._lup }
- MenuListBox._lastvlist = ref(self)
- if not registered_activate_app:
- wx.GetApp().Bind(wx.EVT_ACTIVATE_APP, _activateapp)
- registered_activate_app = True
-
-
-
- def reassign(self, menu):
- self.menu = menu
-
- menuOpenDelayMs = prefprop('menus.submenu_delay', 250)
-
- def __repr__(self):
- return '<%s for %r>' % (self.__class__.__name__, self.menu)
-
-
- def ParentPopup(self):
- pmenu = self.menu._parentmenu
- return None if pmenu is None else pmenu.popup.vlist
-
- ParentPopup = property(ParentPopup)
-
- def CalcSize(self):
- self.SetItemCount(len(self.menu))
- height = 0
- dc = wx.MemoryDC()
- dc.Font = self.font
- s = self.skin
- padx = self.padding[0]
- iconsize = s.iconsize
- subw = s.submenuicon.Width
- sepheight = s.separatorimage.Size.height
- itemheight = self.itemheight
- textExtent = dc.GetTextExtent
- labelw = accelw = 0
- for item in self.menu:
- if item.Kind == ITEM_SEPARATOR:
- height += sepheight
- continue
- height += itemheight
- labelw = max(labelw, textExtent(item.Label)[0])
- accelw = max(accelw, textExtent(item.AccelText)[0])
-
- self.accelColumnX = padx + iconsize + padx + padx + labelw + padx
- width = self.accelColumnX + padx + max(accelw, subw) + padx
- self.MinSize = self.Size = wx.Size(width, height)
-
-
- def OnDrawItem(self, dc, rect, n):
- item = self.menu[n]
- kind = item.Kind
- s = self.skin
- iconsize = s.iconsize
- submenuicon = s.submenuicon
- padx = self.padding.x
- selected = self.IsSelected(n)
- drawbitmap = dc.DrawBitmap
- drawlabel = dc.DrawLabel
- if kind == ITEM_SEPARATOR:
- s.separatorimage.Draw(dc, rect, n)
- else:
- dc.Font = self.font
- if not item.IsEnabled():
- fg = 'disabled'
- elif selected:
- fg = 'selection'
- else:
- fg = 'normal'
- dc.TextForeground = getattr(s.fontcolors, fg)
- grect = Rect(*rect)
- grect.width = padx + iconsize + padx
- bmap = item.Bitmap
- if bmap and bmap.Ok():
- bmap = bmap.ResizedSmaller(iconsize)
- drawbitmap(bmap, grect.HCenter(bmap), rect.VCenter(bmap), True)
-
- if item.IsCheckable() and item.IsChecked():
- if bmap:
- checkx = grect.Right - s.checkedicon.Width
- else:
- checkx = grect.HCenter(s.checkedicon)
- if kind == ITEM_CHECK:
- drawbitmap(s.checkedicon, checkx, rect.VCenter(s.checkedicon), True)
- elif kind == ITEM_RADIO:
- drawbitmap(s.checkedicon, checkx, rect.VCenter(s.checkedicon), True)
-
-
- rect.Subtract(left = iconsize + 3 * padx)
- drawlabel(item.Label, rect, indexAccel = item.Text.split('\t')[0].find('&'), alignment = ALIGN_CENTER_VERTICAL)
- rect.Subtract(right = submenuicon.Width + padx)
- if item.SubMenu is not None:
- drawbitmap(submenuicon, rect.Right, rect.VCenter(submenuicon), True)
-
- acceltext = item.AccelText
- if acceltext:
- rect.x = self.accelColumnX + padx
- drawlabel(acceltext, rect, alignment = ALIGN_CENTER_VERTICAL)
-
-
-
- def OnDrawBackground(self, dc, rect, n):
- s = self.skin
- bgs = s.backgrounds
- bgname = None if self.menu[n].Kind != ITEM_SEPARATOR and self.IsSelected(n) else 'item'
- bg = getattr(bgs, bgname, None)
- if bg:
- bg.Draw(dc, rect, n)
-
-
-
- def PaintMoreBackground(self, dc, rect):
- g = self.skin.backgrounds.gutter
- if g:
- g.Draw(dc, Rect(rect.x, rect.y, self.skin.iconsize + self.padding.x * 2, rect.height))
-
-
-
- def OnMeasureItem(self, n):
- item = self.menu[n]
- kind = item.Kind
- if kind == ITEM_SEPARATOR:
- return self.sepheight
- else:
- return self.itemheight
-
-
- def OnPopup(self):
- if self.menu._windowless and self.TopMenu == self.menu:
- if not hasattr(self, 'traytimer'):
- self.traytimer = UMenuTrayTimer(self)
-
- self.traytimer.Start(50)
-
- if not self.menu._parentmenu:
- self._grabkeyboard()
-
- if wx.LeftDown():
- self._leftbuttondown = True
-
- if not self.HasCapture():
- self.CaptureMouse()
-
- self.SetCursor(StockCursor(CURSOR_DEFAULT))
- self.SetFocus()
-
-
- def Dismiss(self):
- if hasattr(self, 'traytimer'):
- self.traytimer.Stop()
-
- if self.menu._childmenu:
- self.menu._childmenu.Dismiss()
- self.menu._childmenu = None
-
- while self.HasCapture():
- self.ReleaseMouse()
- self.Parent.Hide()
- m = self.menu
- if m._parentmenu is None:
- if hasattr(self, 'focusHandler'):
- self.focusHandler.close()
- del self.focusHandler
-
- wx.CallAfter(self.menu.OnDismiss)
- else:
- m._parentmenu._childmenu = None
-
-
- def DismissRoot(self):
- self.TopMenu.Dismiss()
-
-
- def TopMenu(self):
- m = self.menu
- while m._parentmenu is not None:
- m = m._parentmenu
- return m
-
- TopMenu = property(TopMenu)
-
- def UpdateSkin(self):
- self.SetMargins(wx.Point(0, 0))
- s = self.skin = self.menu.skin
- self.sepheight = s.separatorimage.Size.height
-
- try:
- self.font = s.font
- except KeyError:
- self.font = default_font()
-
- self.fontheight = s.font.Height
-
- try:
- self.padding = s.padding
- except Exception:
- self.padding = wx.Point(3, 3)
-
- self.itemheight = int(self.fontheight + self.padding.y * 2)
- self.Background = s.backgrounds.menu
-
-
- def Window(self):
- return self.menu.Window
-
- Window = property(Window)
-
- def _grabkeyboard(self):
- if 'wxMSW' in wx.PlatformInfo:
- self._focusWin = wx.Window.FindFocus()
- elif 'wxGTK' in wx.Platform:
- self._focusWin = self
- else:
- self._focusWin = None
- f = self._focusWin
- if f:
- self.focusHandler = FocusHandler(self, f)
-
-
-
- def _showsubmenu(self, i, highlight = False):
- item = self.menu[i]
- submenu = item.SubMenu
- child = self.menu._childmenu
- if child is submenu:
- return None
-
- if child is not None:
- if child:
- child.Dismiss()
-
- self.menu._childmenu = None
-
- if i != -1 and submenu is not None:
- r = self.ClientRect
- r.Y = self.GetItemY(i)
- r.Height = self.OnMeasureItem(i)
- self.menu._childmenu = submenu
- submenu._parentmenu = self.menu
- submenu._parentindex = i
- submenu.PopupMenu(r.ToScreen(self), submenu = True)
- if highlight:
- submenu.popup.vlist.Selection = 0
-
-
-
-
- def _on_submenu_timer(self):
- i = self.Selection
- if i != -1 and self.IsShown() and FindWindowAtPointer() is self:
- self._showsubmenu(i)
-
-
-
- def _listbox(self, e):
- self.timer.Start(self.menuOpenDelayMs, True)
-
-
- def _emit_menuevent(self, id, type = wx.wxEVT_COMMAND_MENU_SELECTED):
- event = wx.CommandEvent(type, id)
- self.menu.Handler.AddPendingEvent(event)
-
-
- def _mouseevents(self, e, wxEVT_MOTION = wxEVT_MOTION, FindWindowAtPoint = FindWindowAtPoint, UberButton = UberButton):
- rect = self.ClientRect
- pt = e.Position
- if not rect.Contains(pt):
- menu = self.ParentPopup
- oldmenu = self
- while menu:
- pt = menu.ScreenToClient(oldmenu.ClientToScreen(pt))
- if menu.ClientRect.Contains(pt):
- (e.m_x, e.m_y) = pt
- return menu._mouseevents(e)
-
- oldmenu = menu
- menu = menu.ParentPopup
-
- try:
- button = self.TopMenu._button
- except AttributeError:
- pass
-
- if e.GetEventType() == wxEVT_MOTION:
- ctrl = FindWindowAtPoint(self.ClientToScreen(e.Position))
- if ctrl is not None:
- if getattr(self, '_motionswitch', -1) is ctrl:
- self._motionswitch = None
- self.DismissRoot()
- ctrl.menu._showquick = True
- ctrl.OnLeftDown()
- elif isinstance(ctrl, UberButton) and ctrl.menubarmode and hasattr(ctrl, 'menu'):
- if ctrl.Parent is button.Parent and ctrl is not button:
- self._motionswitch = ctrl
-
-
-
-
-
-
- try:
- cb = self.mouseCallbacks[e.EventType]
- except KeyError:
- pass
-
- cb(e)
-
-
- def _motion(self, e):
- p = e.Position
- i = None if self.ClientRect.Contains(p) else -1
- s = self.Selection
- if i != s:
- p = self.ParentPopup
- if p is not None:
- pi = getattr(self.menu, '_parentindex', None)
- if pi is not None and p.Selection != pi:
- p.Selection = pi
-
-
- self.SetSelection(i)
- self._emit_lbox_selection(i)
-
-
-
- def LeafMenu(self):
- s = self.menu
- while s._childmenu:
- s = s._childmenu
- return s
-
- LeafMenu = property(LeafMenu)
-
- def _keydown(self, e):
- self = self.LeafMenu.popup.vlist
- code = e.KeyCode
- i = self.Selection
- j = -1
- m = self.menu
- if code == wx.WXK_DOWN:
- j = (i + 1) % len(m)
- while j != i and m[j].Kind == wx.ITEM_SEPARATOR:
- j = (j + 1) % len(m)
- elif code == wx.WXK_UP:
- if i == -1:
- i = len(m)
-
- j = (i - 1) % len(m)
- while j != i and m[j].Kind == wx.ITEM_SEPARATOR:
- j = (j - 1) % len(m)
- elif code == wx.WXK_RETURN:
- return self._activate_item(i, submenu = True, highlight = True)
- elif code == wx.WXK_RIGHT:
- if i == -1:
- pass
- elif m[i].SubMenu is not None:
- self.timer.Stop()
- return self._showsubmenu(i, highlight = True)
-
- while m._parentmenu:
- m = m._parentmenu
- next = getattr(m, '_next', None)
- if next is not None:
- wx.CallAfter(self.DismissRoot)
- next._showquick = True
- wx.CallAfter(next._button.OnLeftDown)
-
- elif code == wx.WXK_ESCAPE:
- self.Dismiss()
- elif code == wx.WXK_LEFT:
- if m._parentmenu:
- self.Dismiss()
- else:
- prev = getattr(self.menu, '_prev', None)
- if prev is not None:
- wx.CallAfter(self.DismissRoot)
- prev._showquick = True
- wx.CallAfter(prev._button.OnLeftDown)
-
- elif code < 256:
- self._on_char(unichr(e.UnicodeKey))
-
- if j != -1:
- self.SetSelection(j)
-
-
-
- def _on_char(self, char):
- char = char.lower()
- items = []
- for item in self.menu:
- amp_char = GetAmpChar(item)
- if amp_char is not None and char == amp_char.lower():
- return self._activate_item(item, submenu = True, highlight = True)
- continue
-
- items = []
- for i in rotated(range(0, len(self.menu)), -(self.Selection) - 1):
- item = self.menu[i]
- label_text = item.GetItemLabelText()
- if label_text and label_text[0].lower() == char:
- items.append(i)
- continue
-
- if len(items) == 1:
- self._activate_item(items[0], submenu = True, highlight = True)
- elif len(items) > 1:
- self.SetSelection(items[0])
-
-
-
- def _rdown(self, e):
- p = e.Position
- rect = self.ClientRect
- if not rect.Contains(p):
- return self.DismissRoot()
-
-
-
- def _ldown(self, e):
- p = e.Position
- rect = self.ClientRect
- if not rect.Contains(p):
- return self.DismissRoot()
-
- i = self.HitTest(p)
- if i != -1:
- if self.menu[i].SubMenu is not None:
- self.timer.Stop()
- return self._showsubmenu(i)
-
-
-
-
- def _lup(self, e):
- p = e.Position
- i = self.HitTest(e.Position)
- if self.ClientRect.Contains(p):
- self._activate_item(i)
- else:
- ctrl = FindWindowAtPointer()
- if not isinstance(ctrl, UberButton) or not (ctrl.type == 'menu'):
- self.DismissRoot()
-
-
-
- def _activate_item(self, i, submenu = False, highlight = False):
- if isinstance(i, int):
- if i == -1:
- return None
-
- item = self.menu[i]
- else:
- item = i
- i = self.menu.IndexOf(item)
- if submenu:
- if item.SubMenu is not None:
- self.timer.Stop()
- if not self.Selection == i:
- self.SetSelection(i)
-
- return self._showsubmenu(i, highlight = highlight)
-
-
- if item.Kind != ITEM_SEPARATOR and item.IsEnabled() and item.SubMenu is None:
- if item.IsCheckable():
- item.Check(not item.IsChecked())
-
- self._emit_menuevent(item.Id)
- self.DismissRoot()
-
-
-
- def _capturechanged(self, e):
-
- def active():
-
- try:
- if self.menu._windowless or not hasattr(self.menu.Window.Top, 'IsActive'):
- return True
- else:
- return self.menu.Window.Top.IsActive()
- except Exception:
- print_exc()
- return True
-
-
- ((None,), wx.CallAfter)((lambda : None if not active() else None))
-
-
-
- class MenuWindowBase(object):
-
- def __init__(self, parent, menu):
- self.vlist = MenuListBox(self, menu)
- self.UpdateSkin()
- self.SetBackgroundStyle(wx.BG_STYLE_CUSTOM)
- self.Bind(wx.EVT_PAINT, self._paint)
-
-
- def reassign(self, parent, menu):
- self.Reparent(parent)
- self.vlist.reassign(menu)
-
-
- def _paint(self, e):
- dc = wx.BufferedPaintDC(self)
- self.bg.Draw(dc, self.ClientRect)
-
-
- def UpdateSkin(self):
- s = self.skin = self.vlist.menu.skin
- if self.Sizer and not wx.IsDestroyed(self.Sizer):
- self.Sizer.Clear()
-
- self.framesize = s.get('framesize', skin.ZeroMargins)
- self.Sizer = self.framesize.Sizer(self.vlist)
- self.bg = s.frame
-
-
- def PopupMenu(self, pos = None, submenu = False):
- v = self.vlist
- v.menu.Handler._menu_open(menu = v.menu)
- v.SetSelection(-1)
- v.CalcSize()
- self.Fit()
- self.Sizer.Layout()
- if isinstance(self.bg, SplitImage4):
- self.Cut(self.bg.GetBitmap(self.Size))
- else:
- self.Cut()
- pos = None if pos is None else pos
-
- try:
-
- try:
- disp = Monitor.GetFromPoint(pos[:2]).Geometry
- except Exception:
- disp = Monitor.GetFromPoint(pos.BottomRight).Geometry
-
- except Exception:
- print_exc()
- log.critical('could not find display for %s, falling back to zero', pos)
- disp = Monitor.All()[0].Geometry
-
- size = self.Size
- rects = []
-
- add = lambda *seq: []([ RectPS(p, size) for p in seq ])
- singlepoint = len(pos) == 2
- offset = (None, None) if singlepoint else 0
- if singlepoint:
- pos = wx.RectPS(pos, (0, 0))
-
- w = Point(size.width - offset, 0)
- h = Point(0, size.height - offset)
- wh = Point(size.width - offset, size.height - offset)
- difftop = Point(0, self.framesize.top)
- diffbottom = Point(0, self.framesize.bottom)
- if submenu:
- add(pos.TopRight - difftop, pos.TopLeft - w - difftop, (pos.BottomRight - h) + diffbottom, (pos.BottomLeft - wh) + diffbottom)
- else:
- add(pos.BottomLeft, pos.TopLeft - h, pos.BottomRight - w, pos.TopRight - h, pos.TopRight - wh, pos.BottomLeft - h)
- for rect in rects:
- if disp.ContainsRect(rect):
- self._showat(rect)
- return None
- continue
-
- rect = rects[0]
- if hasattr(v.menu, '_button'):
- brect = v.menu._button.ScreenRect
- if rect.Intersects(brect):
- rect.Offset((brect.Width, 0))
-
-
- self._showat(rect)
-
-
- def _showat(self, rect, nofade = False):
- self.SetRect(rect)
- self.EnsureInScreen()
- if nofade:
- self.Show()
- elif getattr(self.vlist.menu, '_showquick', False):
- self.vlist.menu._showquick = False
- self.Show()
- else:
- fadein(self, 'xfast')
- if wxMSW:
- CallLater((1,), (lambda : None if self else None))
-
- self.vlist.OnPopup()
-
-
-
- class MenuPopupWindow(MenuWindowBase, wx.PopupWindow):
-
- def __init__(self, parent, menu):
- wx.PopupWindow.__init__(self, parent)
- MenuWindowBase.__init__(self, parent, menu)
-
-
-
- class MenuFrameWindow(MenuWindowBase, wx.Frame):
-
- def __init__(self, parent, menu):
- wx.Frame.__init__(self, parent)
- MenuWindowBase.__init__(self, parent, menu)
-
-
- from weakref import WeakValueDictionary
-
- class MenuEventHandler(wx.EvtHandler):
-
- def __init__(self, parentFrame):
- wx.EvtHandler.__init__(self)
- parentFrame.PushEventHandler(self)
- self.Bind(wx.EVT_MENU, self._MenuEventHandler__menu)
- if 'wxMac' not in wx.PlatformInfo:
- self.Bind(wx.EVT_MENU_OPEN, self._menu_open)
-
- if 'wxMSW' in wx.PlatformInfo:
- parentFrame.BindWin32(WM_INITMENUPOPUP, self._initmenupopup)
-
- self.cbs = WeakValueDictionary()
- self.showcbs = { }
- if wxMSW:
- self.hwndMap = WeakValueDictionary()
-
-
-
- def AddCallback(self, id, callback):
- self.cbs[id] = callback
-
-
- def AddShowCallback(self, id, callback):
- self.showcbs[id] = callback
-
-
- def __menu(self, e):
- id = e.Id
-
- try:
- cb = self.cbs[id]
- except KeyError:
- e.Skip()
-
- cb()
-
-
- def _menu_open(self, e = None, menu = None):
- if e is not None:
- e.Skip()
- menu = e.Menu
-
- if menu is None:
- return None
-
-
- try:
- cb = self.showcbs[menu.Id]
- except KeyError:
- pass
-
- cb()
-
- if wxMSW:
-
- def _initmenupopup(self, hWnd, msg, wParam, lParam):
-
- try:
- menu = self.hwndMap[wParam]
- except KeyError:
- return None
-
- if menu._parentmenu:
- evt = PyCommandEvent(wxEVT_MENU_OPEN, menu.Id)
- evt.Menu = menu
- menu.Handler.ProcessEvent(evt)
-
-
-
-
-
- class FocusHandler(wx.EvtHandler):
-
- def __init__(self, menu, ctrl):
- wx.EvtHandler.__init__(self)
- self._menu = menu
- self._ctrl = ctrl
- self.Bind(wx.EVT_KEY_DOWN, self._menu._keydown)
- self.Bind(wx.EVT_NAVIGATION_KEY, self._menu._keydown)
- self.wantschars = bool(ctrl.WindowStyleFlag & wx.WANTS_CHARS)
- if not self.wantschars:
- ctrl.SetWindowStyleFlag(ctrl.WindowStyleFlag | wx.WANTS_CHARS)
-
- ctrl.PushEventHandler(self)
-
-
- def close(self):
- ctrl = self._ctrl
- ctrl.RemoveEventHandler(self)
- f = ctrl.WindowStyleFlag
- if not self.wantschars:
- f = f & ~(wx.WANTS_CHARS)
- ctrl.SetWindowStyleFlag(f)
-
-
-
- def SetMenu(self, menu):
- self._menu = menu
-
-
- def OnKeyDown(self, event):
- self._menu.OnKeyDown(event)
-
-
-
- def menuEventHandler(f):
-
- try:
- return f._menuevthandler
- except AttributeError:
- h = f._menuevthandler = MenuEventHandler(f)
-
- return h
-
- from gui.toolbox.keynames import keynames, modifiernames
-
- def menuevt(item):
- return wx.CommandEvent(wx.wxEVT_COMMAND_MENU_SELECTED, item.Id)
-
-
- def GetAccelText(item):
- a = item.Accel
- return None if not a else _getacceltext(a.Flags, a.KeyCode)
-
- if not hasattr(wx, '_MenuItem'):
- wx._MenuItem = wx.MenuItem
-
- wx._MenuItem.AccelText = property(GetAccelText)
-
- def GetAmpChar(item):
- text = item.Text
- amp_index = text.find('&')
- if amp_index != -1 and amp_index < len(text) - 1:
- return text[amp_index + 1]
-
-
-
- def _getacceltext(modifiers, key, joinstr = '+'):
- return [](_[1] + [
- keynames.get(key, chr(key).upper())])
-
- _getacceltext = memoize(_getacceltext)
- from collections import deque
-
- def rotated(iter, n):
- d = deque(iter)
- d.rotate(n)
- return d
-
-